<!--
使用antd原生Form生成 详细用法参考ant-design-vue Form组件文档
vscode默认配置文件会自动格式化/移除未使用依赖
-->
<script setup lang="ts">
import type { RuleObject } from 'ant-design-vue/es/form';
import { computed, ref, watch, h } from 'vue';

import {
  Input,
  Textarea,
  Select,
  RadioGroup,
  CheckboxGroup,
  DatePicker,
  Form,
  FormItem,
  Row,
  Col,
  InputNumber,
  Button,
} from 'ant-design-vue';
import { ImageUpload, FileUpload } from '#/components/upload';
import { Tinymce } from '#/components/tinymce';
import { getPopupContainer } from '@vben/utils';
import { pick } from 'lodash-es';

import { useVbenDrawer } from '@vben/common-ui';
import { $t } from '@vben/locales';
import { cloneDeep } from '@vben/utils';
import { Modal, message } from 'ant-design-vue';

import { useVbenForm } from '#/adapter/form';
import { carCostAdd, carCostInfoByOrderId, carCostUpdate, carCostSubmit, carCostApprove, carCostRemove, carCostInvalidate } from '#/api/trade/carCost';
import type { CarCostForm } from '#/api/trade/carCost/model';
import SaleContractDetails from '../saleContract/components/SaleContractDetails.vue';
import { customerInfo } from '#/api/trade/customer';
import type { CustomerVO } from '#/api/trade/customer/model';
import { useBeforeCloseDiff } from '#/utils/popup';
import type { ID } from '#/api/common';
import { APPROVE_STATUS } from '../constants';

const emit = defineEmits<{ reload: [] }>();

const isUpdate = ref(false);
const title = computed(() => {
  return isUpdate.value ? $t('pages.common.edit') : $t('pages.common.add');
});

// 客户信息
const customerDefault: Partial<CustomerVO> = {
  id: '',
  name: '',
  contact: '',
  contactPhone: '',
  saleUserid: '',
  areaType: '',
  provinceId: '',
  cityId: '',
  districtId: '',
  areaId: [],
  updateBy: 0,
  updateTime: '',
};

/**
 * 定义默认值 用于reset
 */
const defaultValues: Partial<CarCostForm> = {
  id: undefined,
  orderId: undefined,
  deptId: undefined,
  plateCost: undefined,
  checkCost: undefined,
  insuranceCost: undefined,
  vehicleTaxCost: undefined,
  clearCustomsCost: undefined,
  declarationCustomsCost: undefined,
  shipCost: undefined,
  otherCost: undefined,
  otherCostName: undefined,
  totalAmount: undefined,
  attachments: undefined,
  order: undefined,
  status: APPROVE_STATUS.DRAFT,
  rejectReason: undefined,
};

/**
 * 表单数据ref
 */
const formData = ref(defaultValues);
const customerData = ref(customerDefault);

// 附件列表，用于FileUpload组件的双向绑定
const attachmentsList = ref<string[]>([]);

// 处理附件变化
const handleAttachmentsChange = () => {
  // 将数组转换为逗号分割的字符串
  formData.value.attachments = attachmentsList.value.length > 0 
    ? attachmentsList.value.join(',') 
    : undefined;
};

// 监听formData.attachments变化，同步到attachmentsList
watch(
  () => formData.value.attachments,
  (newAttachments) => {
    if (newAttachments && typeof newAttachments === 'string') {
      // 将逗号分割的字符串转换为数组
      attachmentsList.value = newAttachments.split(',').filter(id => id.trim());
    } else {
      attachmentsList.value = [];
    }
  },
  { immediate: true }
);

// 计算总费用
const calculateTotalAmount = () => {
  const {
    plateCost = 0,
    checkCost = 0,
    insuranceCost = 0,
    vehicleTaxCost = 0,
    clearCustomsCost = 0,
    declarationCustomsCost = 0,
    shipCost = 0,
    otherCost = 0
  } = formData.value;
  
  // 将所有费用转为数字并相加
  const total = [
    plateCost,
    checkCost,
    insuranceCost,
    vehicleTaxCost,
    clearCustomsCost,
    declarationCustomsCost,
    shipCost,
    otherCost
  ].reduce((sum, cost) => {
    // 确保cost是数字
    const costValue = parseFloat(cost as string) || 0;
    return sum + costValue;
  }, 0);
  
  // 保留两位小数
  formData.value.totalAmount = total;
};

// 监听费用变化，自动计算总额
watch(
  () => [
    formData.value.plateCost,
    formData.value.checkCost,
    formData.value.insuranceCost,
    formData.value.vehicleTaxCost,
    formData.value.clearCustomsCost,
    formData.value.declarationCustomsCost,
    formData.value.shipCost,
    formData.value.otherCost
  ],
  () => calculateTotalAmount(),
  { immediate: true, deep: true }
);

type AntdFormRules<T> = Partial<Record<keyof T, RuleObject[]>> & {
  [key: string]: RuleObject[];
};
/**
 * 表单校验规则
 */
const formRules = ref<AntdFormRules<CarCostForm>>({
  plateCost: [{ required: true, message: '上牌过户费不能为空' }],
  checkCost: [{ required: true, message: '检测报告费不能为空' }],
  insuranceCost: [{ required: true, message: '交强险不能为空' }],
  vehicleTaxCost: [{ required: true, message: '车船税不能为空' }],
  clearCustomsCost: [{ required: true, message: '清关费不能为空' }],
  declarationCustomsCost: [{ required: true, message: '报关费不能为空' }],
  shipCost: [{ required: true, message: '运费不能为空' }],
  otherCost: [{ required: true, message: '其他费用不能为空' }],
  otherCostName: [{ required: true, message: '费用名称不能为空' }],
  totalAmount: [{ required: true, message: '费用合计不能为空' }],
});

// 驳回原因是否可见
const showRejectReason = computed(() => {
  return formData.value.rejectReason && formData.value.rejectReason.trim() !== '';
});

// 表单是否禁用 - 只有待提交、已驳回状态下才可以输入
const isFormDisabled = computed(() => {
  console.log('formData.value.status',formData.value.status);

  return formData.value.status !== null &&formData.value.status !== APPROVE_STATUS.DRAFT && formData.value.status !== APPROVE_STATUS.REJECTED;
});
/**
 * useForm解构出表单方法
 */
const { validate, validateInfos, resetFields } = Form.useForm(
  formData,
  formRules,
);

function customFormValueGetter() {
  return JSON.stringify(formData.value);
}

const { onBeforeClose, markInitialized, resetInitialized } = useBeforeCloseDiff(
  {
    initializedGetter: customFormValueGetter,
    currentGetter: customFormValueGetter,
  },
);

const [BasicDrawer, drawerApi] = useVbenDrawer({
  class: 'w-[1000px]',
  onBeforeClose,
  onClosed: handleClosed,
  onConfirm: handleConfirm,
  onOpenChange: async (isOpen) => {
    if (!isOpen) {
      return null;
    }
    drawerApi.drawerLoading(true);

    const { orderId } = drawerApi.getData() as { orderId: ID };
    const record = await carCostInfoByOrderId(orderId);
    isUpdate.value = !!record.id;

    // 只赋值存在的字段
    const filterRecord = pick(record, Object.keys(defaultValues));
    formData.value = filterRecord;

    // 获取客户信息来显示客户名称
    if (record.order?.saleContract?.customerId) {
      try {
        const customerInfoData = await customerInfo(
          record.order.saleContract.customerId,
        );
        if (customerInfoData) {
          customerData.value = customerInfoData;
        }
      } catch (error) {
        console.error('获取客户详情失败', error);
      }
    }
    await markInitialized();

    drawerApi.drawerLoading(false);
  },
});

async function handleConfirm() {
  try {
    drawerApi.lock(true);
    await validate();
    // 可能会做数据处理 使用cloneDeep深拷贝
    const data = cloneDeep(formData.value);
    await (isUpdate.value ? carCostUpdate(data) : carCostAdd(data));
    resetInitialized();
    emit('reload');
    drawerApi.close();
  } catch (error) {
    console.error(error);
  } finally {
    drawerApi.lock(false);
  }
}

async function handleClosed() {
  formData.value = defaultValues;
  customerData.value = customerDefault;
  resetFields();
  resetInitialized();
}

// 审核通过
async function handleApprove() {
  Modal.confirm({
    title: '确认审核通过？',
    content: '审核通过后将无法修改，请确认操作',
    onOk: async () => {
      try {
        await carCostApprove(formData.value.id!, true, undefined);
        message.success('审核通过成功');
        emit('reload');
        drawerApi.close();
      } catch (error) {
        console.error('审核通过失败', error);
      }
    },
  });
}

// 驳回
async function handleReject() {
  Modal.confirm({
    title: '请输入驳回原因',
    content: h(Input.TextArea, {
      placeholder: '请输入驳回原因',
      rows: 4,
      onInput: (e: Event) => {
        rejectReason.value = (e.target as HTMLTextAreaElement).value;
      },
    }),
    onOk: async () => {
      if (!rejectReason.value.trim()) {
        message.warning('请输入驳回原因');
        return Promise.reject();
      }
      try {
        await carCostApprove(formData.value.id!,false, rejectReason.value);
        message.success('驳回成功');
        emit('reload');
        drawerApi.close();
      } catch (error) {
        console.error('驳回失败', error);
      }
    },
  });
}

// 提交
async function handleSubmit() {
  try {
    drawerApi.lock(true);
    await validate();
    const data = cloneDeep(formData.value);
    await carCostUpdate(data);
    await carCostSubmit([data.id!]);
    message.success('重新提交成功');
    resetInitialized();
    emit('reload');
    drawerApi.close();
  } catch (error) {
    console.error('重新提交失败', error);
  } finally {
    drawerApi.lock(false);
  }
}

// 作废
async function handleCancel() {
  Modal.confirm({
    title: '确认作废？',
    content: '作废后将无法恢复，请确认操作',
    onOk: async () => {
      try {
        await carCostInvalidate(formData.value.id!);
        message.success('作废成功');
        emit('reload');
        drawerApi.close();
      } catch (error) {
        console.error('作废失败', error);
      }
    },
  });
}

const rejectReason = ref('');
</script>

<template>
  <BasicDrawer :title="title">
    <template #footer>
      <div class="flex justify-between">
        <!-- 操作按钮 -->
        <div class="flex space-x-3">
          <Button v-if="formData.status === APPROVE_STATUS.DRAFT || formData.status === APPROVE_STATUS.REJECTED" type="primary" @click="handleSubmit">提交审核</Button>
          <Button v-if="formData.status === APPROVE_STATUS.WAITING" type="primary" @click="handleApprove">通过</Button>
          <Button v-if="formData.status === APPROVE_STATUS.WAITING" danger @click="handleReject">驳回</Button>
          <Button v-if="formData.status === APPROVE_STATUS.DRAFT ||  formData.status === APPROVE_STATUS.REJECTED" danger @click="handleCancel">作废</Button>
          <Button  v-if="!formData.status || formData.status === APPROVE_STATUS.DRAFT || formData.status === APPROVE_STATUS.REJECTED" type="primary" @click="handleConfirm">仅保存</Button>
          <Button @click="drawerApi.close()">返回</Button>
        </div>
        
      </div>
    </template>
    <!-- 订单详情 -->
    <Form
      :label-col="{ span: 6 }"
      :wrapper-col="{ span: 18 }"
      v-if="formData.order"
    >
      <Row :gutter="16">
        <Col :span="12">
          <FormItem label="订单编号">
            <Input
              v-model:value="formData.order.orderNo"
              :placeholder="$t('ui.formRules.required')"
              disabled
            />
          </FormItem>
        </Col>
        <Col :span="12">
          <FormItem label="客户名称">
            <Input
              v-model:value="customerData.name"
              :placeholder="$t('ui.formRules.required')"
              disabled
            />
          </FormItem>
        </Col>
      </Row>

      <Row>
        <!-- 销售明细部分 -->
        <Col :span="24">
          <FormItem :wrapper-col="{ span: 24 }" :label-col="{ span: 0 }">
            <SaleContractDetails
              v-model="formData.order.saleContract!.details!"
              :disabled="true"
              :showActions="false"
              :show-frame-no="true"
              :frameNoEditable="false"
            />
          </FormItem>
        </Col>
      </Row>
    </Form>
    <div class="cost-detail">
      <div class="cost-detail-header">
        <h4 >费用详情</h4>
      </div>
      <Form :label-col="{ span: 10 }" :wrapper-col="{ span: 14 }" :validate-trigger="[]">
        <Row :gutter="16">
          <Col :span="8">
            <FormItem label="上牌过户费" v-bind="validateInfos.plateCost">
              <InputNumber
                v-model:value="formData.plateCost"
                :placeholder="$t('ui.formRules.required')"
                :disabled="isFormDisabled"
                 class="w-full"
              />
            </FormItem>
          </Col>
          <Col :span="8">
            <FormItem label="检测报告费" v-bind="validateInfos.checkCost">
              <InputNumber
                v-model:value="formData.checkCost"
                :placeholder="$t('ui.formRules.required')"
                :disabled="isFormDisabled"
                 class="w-full"
              />
            </FormItem>
          </Col>
          <Col :span="8">
            <FormItem label="交强险" v-bind="validateInfos.insuranceCost">
              <InputNumber
                v-model:value="formData.insuranceCost"
                :placeholder="$t('ui.formRules.required')"
                :disabled="isFormDisabled"
                 class="w-full"
              />
            </FormItem>
          </Col>
        </Row>
        <Row :gutter="16">
          <Col :span="8">
            <FormItem label="车船税" v-bind="validateInfos.vehicleTaxCost">
              <InputNumber
                v-model:value="formData.vehicleTaxCost"
                :placeholder="$t('ui.formRules.required')"
                :disabled="isFormDisabled"
                 class="w-full"
              />
            </FormItem>
          </Col>
          <Col :span="8">
            <FormItem label="清关费" v-bind="validateInfos.clearCustomsCost">
              <InputNumber
                v-model:value="formData.clearCustomsCost"
                :placeholder="$t('ui.formRules.required')"
                :disabled="isFormDisabled"
                 class="w-full"
              />
            </FormItem>
          </Col>
          <Col :span="8">
            <FormItem
              label="报关费"
              v-bind="validateInfos.declarationCustomsCost"
            >
              <InputNumber
                v-model:value="formData.declarationCustomsCost"
                :placeholder="$t('ui.formRules.required')"
                :disabled="isFormDisabled"
                 class="w-full"
              />
            </FormItem>
          </Col>
        </Row>
        <Row :gutter="16">
          <Col :span="8">
            <FormItem label="运费" v-bind="validateInfos.shipCost">
              <InputNumber
                v-model:value="formData.shipCost"
                :placeholder="$t('ui.formRules.required')"
                :disabled="isFormDisabled"
                 class="w-full"
              />
            </FormItem>
          </Col>
          <Col :span="8">
            <FormItem label="其他费用" v-bind="validateInfos.otherCost">
              <InputNumber
                v-model:value="formData.otherCost"
                :placeholder="$t('ui.formRules.required')"
                :disabled="isFormDisabled"
                 class="w-full"
              />
            </FormItem>
          </Col>
          <Col :span="8">
            <FormItem label="费用名称" v-bind="validateInfos.otherCostName">
              <Input
                v-model:value="formData.otherCostName"
                :placeholder="$t('ui.formRules.required')"
                :disabled="isFormDisabled"
              />
            </FormItem>
          </Col>
        </Row>
        <Row :gutter="16">
          <Col :span="8">
            <FormItem label="费用合计" v-bind="validateInfos.totalAmount">
              <Input
                v-model:value="formData.totalAmount"
                :placeholder="$t('ui.formRules.required')"
                readonly
                class="bg-gray-50"
              />
            </FormItem>
          </Col>
        </Row>
        <!-- 费用附件单独一行，因为可能需要更多空间 -->
        <Row>
          <Col :span="24">
            <FormItem label="费用附件" v-bind="validateInfos.attachments" :label-col="{ span: 3 }" :wrapper-col="{ span: 21 }">
              <FileUpload 
                :max-count="1" 
                v-model:value="attachmentsList" 
                @change="handleAttachmentsChange"
                accept=".jpg,.jpeg,.png,.gif,.webp,.xlsx,.csv,.docx,.pdf"
                :disabled="isFormDisabled"
              />
            </FormItem>
          </Col>
        </Row>
         <!-- 驳回原因字段，仅在有驳回原因时显示 -->
      <Row v-if="showRejectReason">
        <Col :span="24">
          <FormItem
            label="驳回原因"
            :label-col="{ span: 3 }"
            :wrapper-col="{ span: 21 }"
          >
            <Textarea
              v-model:value="formData.rejectReason"
              :rows="3"
              placeholder="驳回原因"
              disabled
              :maxlength="200"
              show-count
            />
          </FormItem>
        </Col>
      </Row>
      </Form>
    </div>
  </BasicDrawer>
</template>
<style scoped>
.cost-detail {
  border: 1px solid #d9d9d9;
  border-radius: 6px;
  padding: 10px;
  /* background-color: #fafafa; */
}

.cost-detail-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: 16px;
  padding-bottom: 16px;
  border-bottom: 1px solid #f0f0f0;

}
.cost-detail-header h4{
    margin: 0;
    font-size: 16px;
    font-weight: 600;
    color: #262626;
  }
</style>
